package com.central.apps.handler.timeTask.inspcriterion;

import com.central.app.common.quartz.QuartzJob;
import com.central.app.common.util.DateUtils;
import com.central.app.service.HandlerService;
import com.central.apps.dao.inspection.InspplanDao;
import com.central.bizcommon.model.schedule.JobParams;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.collections.MapUtils;
import org.quartz.DisallowConcurrentExecution;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.*;

@Component
@Slf4j
//禁止并发执行(Quartz不要并发地执行同一个job定义（这里指一个job类的多个实例）)
@DisallowConcurrentExecution
public class InspplanTask extends QuartzJob {
    @Autowired
    private InspplanDao inspplanDao;
    @Autowired
    private HandlerService handlerService;

    private String dateStr;
    /**
     * 点检计划生成生成点检任务
     * @param context
     * @param jobnum
     * @param jobname
     * @param jobparams
     * @throws JobExecutionException
     */
    @Override
    public void executeJob(JobExecutionContext context, String jobnum, String jobname, List<JobParams> jobparams) throws JobExecutionException {
        /**
         * 匹配今日需要执行的点检计划，批量生成点检工单
         */
        handlerService.findBySql("insert into tb_task_log(task_describe) values('匹配今日需要执行的点检计划，批量生成点检工单')");
        dateStr = DateUtils.dateToStr(new Date(), "yyyy-MM-dd");
        List<Map<String, Object>> inspplanList = inspplanDao.findInspplanList(dateStr);
        if (CollectionUtils.isEmpty(inspplanList)) {
            log.info("今日没有需要执行的点检计划");
        }else {
            //循环生成点检任务
            for (int i = 0; i < inspplanList.size(); i++) {
                doCreateInsptaskByinspplan(inspplanList.get(i));
            }
            //查当前日期需要更新下一到期日的点检计划
            doUpdateNextexecutedate(inspplanList);
        }
    }
    public void doCreateInsptaskByinspplan(Map<String, Object> inspplanMap) {
        //生成点检任务
        String id = "";
        Map<String, Object> insptaskMap = new HashMap<>();
        handlerService.addBizNum("insptaskApp","gq_insptask", insptaskMap);   //生成编码
        insptaskMap.put("abstract", MapUtils.getString(inspplanMap, "") + dateStr);//描述
        insptaskMap.put("inststarttime", dateStr + " 0:00:00");        //任务开始时间
        insptaskMap.put("instendtime", dateStr + " 23:59:59");         //任务结束时间
        insptaskMap.put("instcheckpost", "日常点检");                   //任务岗位
        insptaskMap.put("instectionters", MapUtils.getString(inspplanMap, "inspectionpers"));//任务人员
        insptaskMap.put("totaldevices", "");                          //设备总数
        insptaskMap.put("abnormal", 0);                               //异常项目数
        insptaskMap.put("testers", 0);                                //设备漏检数
        insptaskMap.put("orgcode", MapUtils.getString(inspplanMap, "orgcode"));
        insptaskMap.put("orgdesc", MapUtils.getString(inspplanMap, "orgdesc"));
        insptaskMap.put("sitecode", MapUtils.getString(inspplanMap, "sitecode"));
        insptaskMap.put("sitedesc", MapUtils.getString(inspplanMap, "sitedesc"));
        insptaskMap.put("deptcode", MapUtils.getString(inspplanMap, "deptcode"));
        insptaskMap.put("deptdesc", MapUtils.getString(inspplanMap, "deptdesc"));
        insptaskMap.put("createuser", "1");                         //创建人
        insptaskMap.put("createtime", new Date());                  //创建时间
        insptaskMap.put("delflag", "0");
        try {
            Object insptaskId = handlerService.insert("gq_insptask", insptaskMap);
            id = insptaskId.toString();
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
        //计划区域生成任务区域
        String inspplannum = MapUtils.getString(inspplanMap, "inspplannum");
        //查区域
        List<Map<String, Object>> planareaList = inspplanDao.findPlanareaListByInspplannum(inspplannum);
        if (CollectionUtils.isNotEmpty(planareaList)) {
            for (int i = 0; i < planareaList.size(); i++) {
                doCreateInsptare(planareaList.get(i), insptaskMap.get("insptasknum").toString());
            }
        }
    }
    public void doCreateInsptare(Map<String, Object> planareaMap, String insptasknum) {
        //循环生成任务区域
        Map<String, Object> insptareaMap = new HashMap<>();
        insptareaMap.put("insptasknum", insptasknum);//关联关系
        insptareaMap.put("insaenum", MapUtils.getString(planareaMap, "insaenum"));      //区域编号
        insptareaMap.put("insaedesc", MapUtils.getString(planareaMap, "insaedesc"));    //区域描述
        String planareaId = MapUtils.getString(planareaMap, "id");                      //计划区域id
        String insptareaId = "";
        try {
            insptareaId = handlerService.insert("gq_insptarea", insptareaMap).toString();
        } catch (Exception e) {
            throw new RuntimeException(e);
        }

        //根据计划区域id查资产
        List<Map<String, Object>> planassetListByPlanareaid = inspplanDao.findPlanassetListByPlanareaid(planareaId);
        if (CollectionUtils.isNotEmpty(planassetListByPlanareaid)) {
            for (int i = 0; i < planassetListByPlanareaid.size(); i++) {
                //生成资产
                doCreateInsptstand(planassetListByPlanareaid.get(i), insptareaId);
            }
        }
    }

    public void doCreateInsptstand(Map<String, Object> planassetMap, String insptareaId) {
        Map<String, Object> insptstandMap = new HashMap<>();
        insptstandMap.put("insptareaId", insptareaId);   //关联关系
        insptstandMap.put("assetnum", MapUtils.getString(planassetMap, "assetnum"));                //资产编号
        insptstandMap.put("assetdesc", MapUtils.getString(planassetMap, "assetdesc"));              //资产描述
        insptstandMap.put("inspnum", MapUtils.getString(planassetMap, "inspnum"));                  //点检编号
        insptstandMap.put("inspdesc", MapUtils.getString(planassetMap, "inspdesc"));                //点检描述
        try {
            handlerService.insert("gq_insptstand", insptstandMap);
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }

    public void doUpdateNextexecutedate(List<Map<String, Object>> inspplanList) {
        for (int i = 0; i < inspplanList.size(); i++) {
            Map<String, Object> inspplanMap = inspplanList.get(i);
            String id = MapUtils.getString(inspplanMap, "id");
            String frequency = MapUtils.getString(inspplanMap, "frequency");               //周期
            String frequencyunit = MapUtils.getString(inspplanMap, "frequencyunit");           //周期单位
            String nextexecutedate = MapUtils.getString(inspplanMap, "nextexecutedate");   //下次执行日期
            Integer intFrequency = Integer.parseInt(frequency);
            Integer dateNum = null;
            Integer CalendarType = null;
            switch (frequencyunit) {
                case "2":
                    //周期为日
                    dateNum = intFrequency * 1;
                    CalendarType = 5;
                    break;
                case "3":
                    //周期为周
                    dateNum = intFrequency * 7;
                    CalendarType = 5;
                    break;
                case "4":
                    //月
                    dateNum = intFrequency;
                    CalendarType = 2;
                    break;
                case "5":
                    //年
                    dateNum = intFrequency;
                    CalendarType = 1;
                    break;
                default:
                    break;
            }
            if (dateNum != null) {
                SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
                Date date = null;
                try {
                    date = dateFormat.parse(nextexecutedate);
                } catch (ParseException e) {
                    throw new RuntimeException(e);
                }
                Calendar calendar = Calendar.getInstance();
                calendar.setTime(date);
                calendar.add(CalendarType, dateNum);
                Date resultDate = calendar.getTime();
                //下次执行时间
                String newNextDate = dateFormat.format(resultDate);
                //更新点检计划中下次执行时间和上次执行时间
                inspplanDao.updateExecutedate(newNextDate, nextexecutedate, id);
            }
        }
    }
}
